package com.hqully.labmanage.service.impl;

import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.hqully.labmanage.common.enums.ResultEnum;
import com.hqully.labmanage.common.exception.DAOException;
import com.hqully.labmanage.common.exception.ResultException;
import com.hqully.labmanage.domain.dto.LaboratoryDTO;
import com.hqully.labmanage.domain.dto.PageDTO;
import com.hqully.labmanage.domain.entity.Laboratory;
import com.hqully.labmanage.domain.entity.OpeningHour;
import com.hqully.labmanage.mapper.LaboratoryMapper;
import com.hqully.labmanage.mapper.OpeningHourMapper;
import com.hqully.labmanage.service.LaboratoryService;
import com.hqully.labmanage.service.impl.constant.MapperConst;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.dao.DuplicateKeyException;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.List;

/**
 * <p>
 * 针对数据库表[laboratory]的操作Service
 * </p>
 *
 * @entity {@link Laboratory}
 * @date 2022-10-08 10:05:23 <br>
 * @author hqully <br>
 * @version 1.0
 */
@Slf4j
@Service
public class LaboratoryServiceImpl implements LaboratoryService {


    @Resource
    private LaboratoryMapper laboratoryMapper;

    @Resource
    private OpeningHourMapper openingHourMapper;

    @Override
    public PageInfo<LaboratoryDTO> pageLaboratorys(PageDTO page, LaboratoryDTO laboratoryDTO) {
        try {
            PageHelper.startPage(page);
            List<LaboratoryDTO> laboratoryList = laboratoryMapper.listLaboratories(laboratoryDTO);
            return new PageInfo<>(laboratoryList);
        } catch (Exception e) {
            log.error("PAGE [laboratory] FAIL\nINPUT OBJECT: {}\nREASON: {}", laboratoryDTO, e.toString());
            throw new ResultException(ResultEnum.ERROR, "查询实验室分页列表失败");
        }
    }

    @Override
    public List<LaboratoryDTO> listLaboratorys(LaboratoryDTO laboratoryDTO) {
        try {
            return laboratoryMapper.listLaboratories(laboratoryDTO);
        } catch (Exception e) {
            log.error("LIST [laboratory] FAIL\nINPUT OBJECT: {}\nREASON: {}", laboratoryDTO, e.toString());
            throw new ResultException(ResultEnum.ERROR, "查询实验室列表失败");
        }
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public int addLaboratory(LaboratoryDTO laboratoryDTO) {
        Laboratory laboratory = new Laboratory();
        BeanUtils.copyProperties(laboratoryDTO, laboratory);

        List<OpeningHour> openingSchedule = laboratoryDTO.getOpeningSchedule();
        openingSchedule.forEach(openingHour -> openingHour.setLabId(laboratory.getLabId()));

        int status;
        try {
            // 更新实验室的开放时间
            openingHourMapper.batchInsertOrUpdateOpeningHour(openingSchedule);
            status = laboratoryMapper.addLaboratory(laboratory);
        } catch (DuplicateKeyException e) {
            log.warn("ADD [laboratory] FAIL\nINPUT OBJECT: {}\nREASON: {}", laboratoryDTO, e.toString());
            throw new ResultException(ResultEnum.DUPLICATE_KEY_CONFLICT, "添加实验室失败\n原因: 实验室id已存在");
        } catch (Exception e) {
            log.error("ADD [laboratory] FAIL\nINPUT OBJECT: {}\nREASON: {}", laboratoryDTO, e.toString());
            throw new ResultException(ResultEnum.ERROR, "添加实验室失败");
        }
        return status;
    }

    @Override
    public int updateLaboratory(LaboratoryDTO laboratoryDTO) {
        Laboratory laboratory = new Laboratory();
        BeanUtils.copyProperties(laboratoryDTO, laboratory);

        List<OpeningHour> openingSchedule = laboratoryDTO.getOpeningSchedule();

        int status;
        try {
            // 更新实验室的开放时间
            openingHourMapper.batchInsertOrUpdateOpeningHour(openingSchedule);
            status = laboratoryMapper.updateLaboratory(laboratory);
            if (status == MapperConst.OBJECT_NULL) {
                throw new DAOException("this [laboratory] record not exist");
            }
        }catch (DAOException e){
            log.warn("UPDATE [laboratory] FAIL\nINPUT OBJECT: {}\nREASON: {}", laboratoryDTO, e.toString());
            throw new ResultException(ResultEnum.RESULT_NULL, "更新实验室失败\n原因: 实验室不存在");
        }
        catch (Exception e) {
            log.error("UPDATE [laboratory] FAIL\nINPUT OBJECT: {}\nREASON: {}", laboratoryDTO, e.toString());
            throw new ResultException(ResultEnum.ERROR, "更新实验室失败");
        }
        return status;
    }

    @Override
    public int deleteLaboratoryById(String labId ) {
        int status;
        try {
            status = laboratoryMapper.deleteLaboratoryById(labId);
            if (status == MapperConst.OBJECT_NULL) {
                throw new DAOException("this [laboratory] record not exist");
            }
        } catch (DAOException e) {
            log.warn("DELETE [laboratory] FAIL\nINPUT OBJECT: {}\nREASON: {}", labId, e.toString());
            throw new ResultException(ResultEnum.RESULT_NULL, "删除实验室失败\n原因: 实验室不存在");
        } catch (Exception e) {
            log.error("DELETE [laboratory] FAIL\nINPUT OBJECT: {}\nREASON: {}", labId, e.toString());
            throw new ResultException(ResultEnum.ERROR, "删除实验室失败");
        }
        return status;
    }


}



